package cn.lsj.lock.client;


import org.apache.curator.framework.CuratorFramework;
import org.apache.curator.utils.CloseableUtils;
import org.apache.zookeeper.CreateMode;
import org.apache.zookeeper.Watcher;
import org.apache.zookeeper.data.Stat;

import java.util.Collections;
import java.util.List;

public class DefaultZKClient implements ZKClient {

    private final CuratorFramework client;


    public DefaultZKClient(CuratorFramework client) {
        this.client = client;
        this.client.start();
    }

    public void destroy() {
        CloseableUtils.closeQuietly(client);
    }


    /**
     * 创建节点
     */
    public void createNode(String zkPath, String data) {
        try {
            // 创建一个 ZNode 节点
            // 节点的数据为 payload
            byte[] payload = "to set content".getBytes("UTF-8");
            if (data != null) {
                payload = data.getBytes("UTF-8");
            }
            client.create().creatingParentsIfNeeded().withMode(CreateMode.PERSISTENT).forPath(zkPath, payload);

        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    /**
     * 删除节点
     */
    public void deleteNode(String zkPath) {
        try {
            if(zkPath == null || zkPath.length() == 0) {
                return;
            }
            if (!isNodeExist(zkPath)) {
                return;
            }
            client.delete().forPath(zkPath);

        } catch (Exception e) {
            e.printStackTrace();
        }
    }


    /**
     * 检查节点
     */
    public boolean isNodeExist(String zkPath) {
        try {

            Stat stat = client.checkExists().forPath(zkPath);
            if (null == stat) {
                return false;
            } else {
                return true;

            }

        } catch (Exception e) {
            e.printStackTrace();
        }
        return false;
    }

    /**
     * 创建 临时 顺序 节点
     */
    public String createEphemeralSeqNode(String srcpath) {
        try {

            // 创建一个 ZNode 节点
            return client.create().creatingParentsIfNeeded().withMode(CreateMode.EPHEMERAL_SEQUENTIAL).forPath(srcpath);

        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    public List<String> getWaiters(String path) {
        List<String> children = null;
        try {
            children = client.getChildren().forPath(path);
        } catch (Exception e) {
            e.printStackTrace();
            return Collections.emptyList();
        }
        return children;
    }

    public void watcher(Watcher w, String path) throws Exception {
        // TODO 未处理异常 org.apache.zookeeper.KeeperException$NoNodeException: KeeperErrorCode = NoNode
        client.getData().usingWatcher(w).forPath(path);
    }
}
